package com.jadows.tdog.repository;

import cn.hutool.core.collection.CollUtil;
import com.jadows.tdog.domain.ChatMessage;
import com.jadows.tdog.util.SecurityUtil;
import lombok.Data;
import org.springframework.data.domain.Sort;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.aggregation.Aggregation;
import org.springframework.data.mongodb.core.aggregation.AggregationOperation;
import org.springframework.data.mongodb.core.aggregation.AggregationResults;
import org.springframework.data.mongodb.core.aggregation.ConditionalOperators;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.core.query.Update;
import org.springframework.data.mongodb.repository.MongoRepository;
import org.springframework.stereotype.Repository;

import java.util.List;

/**
 * @author taojiacheng
 */
@Repository
public interface ChatMessageRepository extends MongoRepository<ChatMessage, Long> {


    /**
     * 查询联系人分组的最近10条聊天记录
     */
    default List<ChatMessageGroup> findLast10MessageByUnionIdIn(MongoTemplate mongoTemplate, List<String> unionIds) {
        if (CollUtil.isEmpty(unionIds)) {
            return CollUtil.newArrayList();
        }
        String memberId = SecurityUtil.getCurrentUser().getMemberId();
        // 按照 unionId 分组，每组取10条
        // 构建聚合查询操作
        AggregationOperation matchOperation = Aggregation.match(Criteria.where("unionId").in(unionIds));
        AggregationOperation sortOperation = Aggregation.sort(Sort.Direction.DESC, "_id");
        // 按照 unionId 分组，每组取10条
        AggregationOperation groupOperation = Aggregation.group("unionId")
                .push("$$ROOT").as("messages")
                //  "unreadCount" : { "$sum" : { "$cond" : { "if" : { "$and" : [{ "$eq" : ["$fromUid", "1ee8958d20ea64fe9259932f15895def"]}, { "$eq" : ["$isRead", true]}]}, "then" : 1, "else" : 0}}}}}
                .sum(ConditionalOperators
                        .when(new Criteria().andOperator(
                                Criteria.where("fromUid").ne(memberId),
                                Criteria.where("isRead").is(false))
                        )
                        .then(1)
                        .otherwise(0))
                .as("unreadCount");

        // project 阶段，将 _id 重命名为 unionId
        AggregationOperation projectOperation = Aggregation.project()
                .and("_id").as("unionId")
                .and("messages").slice(10).as("messages")
                .and("unreadCount").as("unreadCount");
        Aggregation aggregation = Aggregation.newAggregation(matchOperation, sortOperation, groupOperation, projectOperation);
        // 执行聚合查询
        AggregationResults<ChatMessageGroup> result = mongoTemplate.aggregate(aggregation, "chat_messages", ChatMessageGroup.class);
        // 从结果中提取数据
        return result.getMappedResults();
    }


    ChatMessage findFirstByUnionIdOrderByMessageIdDesc(String unionId);

    /**
     * 更新消息为已读
     */
    default void updateIsReadWhenDeletedContact(MongoTemplate mongoTemplate, String unionId, String targetId, Long deletedMessageId) {
        // 将对方发送的消息都设置为已读
        Query query = new Query();
        query.addCriteria(Criteria.where("unionId").is(unionId));
        query.addCriteria(Criteria.where("isRead").is(false));
        query.addCriteria(Criteria.where("fromUid").is(targetId));
        query.addCriteria(Criteria.where("messageId").lte(deletedMessageId));
        Update update = new Update();
        update.set("isRead", true);
        mongoTemplate.updateMulti(query, update, ChatMessage.class);
    }


    @Data
    class ChatMessageGroup {
        private String unionId;
        private List<ChatMessage> messages;
        private Integer unreadCount;
    }

}
